package sk.tuke.utils;

import java.util.ArrayList;
import java.util.List;

import sk.tuke.domain.Address;
import sk.tuke.domain.Department;
import sk.tuke.domain.Diagnose;
import sk.tuke.domain.Disease;
import sk.tuke.domain.Doctor;
import sk.tuke.domain.Drug;
import sk.tuke.domain.HealthCard;
import sk.tuke.domain.Insurance;
import sk.tuke.domain.MedicalNote;
import sk.tuke.domain.MedicalRecord;
import sk.tuke.domain.Patient;
import sk.tuke.domain.Phone;
import sk.tuke.domain.Status;
import sk.tuke.domain.Symptom;
import sk.tuke.domain.User;
import sk.tuke.persistance.AddressPo;
import sk.tuke.persistance.DepartmentPo;
import sk.tuke.persistance.DiagnosePo;
import sk.tuke.persistance.DoctorPo;
import sk.tuke.persistance.DrugPo;
import sk.tuke.persistance.HealthCardPo;
import sk.tuke.persistance.InsurancePo;
import sk.tuke.persistance.MedicalNotePo;
import sk.tuke.persistance.MedicalRecordPo;
import sk.tuke.persistance.PatientPo;
import sk.tuke.persistance.PhonePo;
import sk.tuke.persistance.SymptomPo;
import sk.tuke.persistance.UserPo;

public class MapperPOtoDomain {

	public User mapUserPoToUser(UserPo userPo) throws Exception {
		User user = null;
		if (userPo instanceof DoctorPo) {
			user = new Doctor();
		} else if (userPo instanceof PatientPo) {
			user = new Patient();
		} else {
			throw new Exception("Unknown entity: " + userPo);
		}

		user.setSalutation(userPo.getSalutation());
		user.setFirstname(userPo.getFirstname());
		user.setMiddlename(userPo.getMiddlename());
		user.setLastname(userPo.getLastname());
		List<Address> addresses = new ArrayList<Address>();
		for (AddressPo addressPo : userPo.getAddress()) {
			addresses.add(mapAddressPoToAddress(addressPo));
		}
		user.setAddress(addresses);
		List<Phone> phones = new ArrayList<Phone>();
		for (PhonePo phonePo : userPo.getPhone()) {
			phones.add(mapPhoneToPhonePo(phonePo));
		}
		user.setPhone(phones);
		user.setNumber(userPo.getNumber());
		user.setPassword(userPo.getPassword());
		user.setEmail(userPo.getEmail());
		if (user instanceof Doctor) {
			((Doctor) user).setInsuranceNumber(userPo.getInsurance().getNumber());
			((Doctor) user).setDepartmentNumber(((DoctorPo) userPo).getDepartment().getNumber());
		} else if (user instanceof Patient) {
			((Patient) user).setInsuranceNumber(userPo.getInsurance().getNumber());
			((Patient) user).setHealthCardNumber(((PatientPo) userPo).getHealthCard().getNumber());
		}

		return user;
	}

	public Address mapAddressPoToAddress(AddressPo addressPo) {
		Address address = new Address();
		address.setCity(addressPo.getCity());
		address.setCountry(addressPo.getCountry());
		address.setName(addressPo.getName());
		address.setStreet(addressPo.getStreet());
		address.setStreetNum(addressPo.getStreetNum());
		address.setZip(addressPo.getZip());
		return address;
	}

	public Phone mapPhoneToPhonePo(PhonePo phonePo) {
		Phone phone = new Phone();
		phone.setPhoneNumber(phonePo.getPhoneNumber());
		return phone;
	}

	public Insurance mapInsuranceToInsurancePo(InsurancePo insurancePo) {
		Insurance insurance = new Insurance();
		insurance.setCity(insurancePo.getCity());
		insurance.setContactPerson(insurancePo.getContactPerson());
		insurance.setEmail(insurancePo.getEmail());
		insurance.setName(insurancePo.getName());
		insurance.setNumber(insurancePo.getNumber());
		insurance.setPhone(insurancePo.getPhone());
		insurance.setState(insurancePo.getState());
		insurance.setStreet(insurancePo.getStreet());
		insurance.setStreetNum(insurancePo.getStreetNum());
		insurance.setZip(insurancePo.getZip());
		return insurance;
	}

	public Department mapDepartmentPoToDepartment(DepartmentPo departmentPo) {
		Department department = new Department();
		department.setDescription(departmentPo.getDescription());
		department.setName(departmentPo.getName());
		department.setNumber(departmentPo.getNumber());
		return department;
	}

	public HealthCard mapHealthCardPoToHealthCard(HealthCardPo healthCardPo) {
		HealthCard healthCard = new HealthCard();
		healthCard.setDateFrom(healthCardPo.getDateFrom());
		healthCard.setDescription(healthCardPo.getDescription());
		healthCard.setName(healthCardPo.getName());
		healthCard.setNumber(healthCardPo.getNumber());

		// Convert set to list
		List<MedicalRecordPo> medicalRecordPos = new ArrayList<MedicalRecordPo>(healthCardPo.getMedicalRecord());

		List<MedicalRecord> medicalRecords = new ArrayList<MedicalRecord>();
		for (MedicalRecordPo medicalRecordPo : medicalRecordPos) {
			medicalRecords.add(mapMedicalRecordPoToMedicalRecord(medicalRecordPo));
		}
		healthCard.setMedicalRecords(medicalRecords);
		return healthCard;
	}

	public MedicalRecord mapMedicalRecordPoToMedicalRecord(MedicalRecordPo medicalRecordPo) {
		MedicalRecord medicalRecord = new MedicalRecord();
		medicalRecord.setDate(medicalRecordPo.getDate());
		medicalRecord.setName(medicalRecordPo.getName());
		medicalRecord.setNumber(medicalRecordPo.getNumber());
		medicalRecord.setDiagnose(mapDiagnosePoToDiagnose(medicalRecordPo.getDiagnose()));
		List<MedicalNote> notes = new ArrayList<MedicalNote>();
		for (MedicalNotePo medicalNotePo : medicalRecordPo.getMedicalNote()) {
			MedicalNote note = new MedicalNote();
			note.setName(medicalNotePo.getName());
			note.setDescription(medicalNotePo.getDescription());
			notes.add(note);
		}
		medicalRecord.setMedicalNotes(notes);
		medicalRecord.setStatus(Status.valueOf(medicalRecordPo.getStatus()));
		return medicalRecord;
	}

	private Diagnose mapDiagnosePoToDiagnose(DiagnosePo diagnosePo) {
		Diagnose diagnose = new Diagnose();
		diagnose.setNumber(diagnosePo.getNumber());
		diagnose.setDescription(diagnosePo.getDescription());
		diagnose.setName(diagnosePo.getName());

		if (diagnosePo.getDisease() != null) {
			Disease disease = new Disease();
			disease.setName(diagnosePo.getDisease().getName());
			disease.setDescription(diagnosePo.getDisease().getDescription());
			diagnose.setDisease(disease);
		}

		List<Drug> drugs = new ArrayList<Drug>();
		List<Symptom> symptoms = new ArrayList<Symptom>();

		if (diagnosePo.getDrugs() != null) {
			for (DrugPo drugPo : diagnosePo.getDrugs()) {
				Drug drug = new Drug();
				drug.setName(drugPo.getName());
				drug.setDescription(drugPo.getDescription());
				drugs.add(drug);
			}
		}
		if (diagnosePo.getSymptoms() != null) {
			for (SymptomPo symptomPo : diagnosePo.getSymptoms()) {
				Symptom symptom = new Symptom();
				symptom.setName(symptomPo.getName());
				symptom.setDescription(symptomPo.getDescription());
				symptoms.add(symptom);
			}
		}
		diagnose.setDrugs(drugs);
		diagnose.setSymptoms(symptoms);
		diagnose.setAmountDrugs(diagnosePo.getAmountDrugs());

		return diagnose;
	}

}
